import re
import time

import listener as listener
from pynput import keyboard

url = 'D:\phpstudy_pro\Extensions\Apache2.4.39\logs/access.log.1650931200'     #日志路径


def read_access(time_flag):        #time_flag，标志位：标志是否第一次读取日志，避免周期性读取，读取重复信息。
    global url_data
    url_data = []
    with open(url,'r') as file:
        url_datas = file.readlines()
        now_time = int(time.time())#当前时间戳
        for data in url_datas:
            data_time = re.findall(r"\[(.+?) +", data)[0]
            time_num = time.mktime(time.strptime(data_time, '%d/%b/%Y:%H:%M:%S')) # 获取日志时间戳

            if time_flag==0:             #第一次，检测日志的所有内容
                url_data = url_datas
            if time_flag==1 and (time_num-now_time+60)>0:     #非第一次检测，周期性读取，读取写入日志时间在60s之内的信息
                url_data.append(data)


def alert(url_blacklist,type):
    f = open("D:\python_Data\Brian_IDS\static\rules\ids-rule-result.txt", "a")
    if type==0:
        f.write('[+]警告：可能存在SQL注入攻击! 攻击IP：'+url_blacklist.split(' ')[0]+':\n')
        f.write('[*]危险的请求内容：' + url_blacklist)
        print('[+]警告：可能存在SQL注入攻击! 攻击IP：'+url_blacklist.split(' ')[0])
        print('[*]危险的请求内容：' + url_blacklist)
    if type==1:
        f.write('[+]警告：可能存在XSS攻击! 攻击IP：'+url_blacklist.split(' ')[0]+':\n')
        f.write('[*]危险的请求内容：' + url_blacklist)
        print('[+]警告：可能存在XSS攻击! 攻击IP：'+url_blacklist.split(' ')[0])
        print('[*]危险的请求内容：' + url_blacklist)
    f.close()

def check():
    # 规则库,黑名单
    global XSS_Check
    XSS_Check = []
    global SQL_Check
    SQL_Check = []
    with open('D:\python_Data\Brian_IDS\static/rules\XSS.txt','r') as file:
        XSS_Check = file.readlines()
    with open('D:\python_Data\Brian_IDS\static/rules\SQL.txt','r') as file:
        SQL_Check = file.readlines()
    for one_url in url_data:            #判断XSS
        for xss in XSS_Check:
            if xss.split('\n')[0].lower() in one_url:
                url_blacklist = one_url
                type = 1 #xss
                alert(url_blacklist,type)
                break

    for one_url in url_data:            #判断XSS
        for sql in SQL_Check:
            if sql.split('\n')[0].lower() in one_url:
                url_blacklist = one_url
                type = 0 #SQL
                alert(url_blacklist,type)
                break
def on_press(key):
    # 如果按下了 <Esc> 键
    if key == keyboard.Key.esc:
        global is_stopped
        is_stopped = True

        # 停止监听
        listener.stop()
if __name__ == '__main__':
    time_flag = 0  # 标志时间戳，第一次扫描时扫描全部日志，第二次扫描,flag=1,只扫描，当前60秒之前的产生的新日志。
    is_stopped = False

    listener = keyboard.Listener(on_press=on_press)
    listener.start()

    print("按下 <Esc> 键退出程序（程序会在下一次检测完毕时退出）~")
    while True:
        print('IDS正在检测...........')
        read_access(time_flag)
        check()
        time_flag = 1  #标志只扫描最新六十秒内的新日志
        time.sleep(60)     #每六十秒检测一次
        if is_stopped:
            print("程序已关闭")
            break